﻿using System;
using System.Collections.Generic;
using System.Net.Sockets;
using System.Text;

namespace GameClient
{
    public class NetIO
    {
        string connect;//连接字符串
        int port;//端口
        Socket socket;
        bool reading = false, writing = false;
        byte[] data = new byte[1024];
        List<byte> cache = new List<byte>();//缓存区
        List<TransModel> models = new List<TransModel>();//传输模型列表
        /// <summary>
        /// 
        /// </summary>
        /// <param name="con">连接字符串</param>
        /// <param name="p">端口</param>
        public NetIO(string con, int p)
        {
            connect = con;
            port = p;
        }
        public void start()
        {
            try
            {
                socket = new Socket(AddressFamily.InterNetwork, SocketType.Stream, ProtocolType.Tcp);
                socket.Connect(connect, port);
                socket.BeginReceive(data, 0, data.Length, SocketFlags.None, ReceiveCallBack, null);
            }
            catch (Exception ex)
            {
                Console.WriteLine(ex.ToString());
            }
        }
        void ReceiveCallBack(IAsyncResult ar)
        {
            int length = socket.EndReceive(ar);
            if (length > 0)
            {
                //处理消息
                byte[] value = new byte[length];
                Buffer.BlockCopy(data, 0, value, 0, length);
                cache.AddRange(value);
                if (!reading)
                {
                    reading = true;
                    read();
                }
                try
                {
                    //循环接受消息
                    socket.BeginReceive(data, 0, data.Length, SocketFlags.None, ReceiveCallBack, null);
                }
                catch (Exception ex)
                {
                    socket.Shutdown(SocketShutdown.Both);
                    socket.Close();
                    Console.WriteLine(ex.ToString());
                }
            }
        }
        public void read()
        {
            byte[] result = Lengthcode.LengthDeCode(ref cache);
            if (result == null)
            {
                reading = false;
                return;
            }
            //传输模型解码
            else
            {
                TransModel model = TransModelCode.TransModelDeCode(result);
                if (model == null)
                {
                    reading = false;
                    return;
                }
                //通知上层应用有消息到达，准备处理model
                models.Add(model);
                Console.WriteLine("{0},,{1},,{2},,{3}",model.type,model.area,model.command,model.GetMessage<string>());
                read();//进行递归，继续读取消息
            }
        }
    }
}